/*
 * Walker and TreeParser
 * Random Data Generator Language (RDGL)
 * by Navid Azimi, Summer 2007
 */

header {package rdgl.antlr;}
{
import java.util.*;
import rdgl.compiler.Engine;
import rdgl.compiler.DataList;
import rdgl.compiler.RandomData;
import rdgl.compiler.DataType;
}

class RDGLWalker extends TreeParser;

options {
    importVocab = RDGL;
}

{
	public void out(String line) {
		//System.out.println(line);
	}
}

expr returns [ RandomData r ]
{
	r = new RandomData();
}
	: #(STATEMENT (smnt:.{ r = expr(#smnt); r.print(); })+)
	| LOOP {
			out("> LOOP");
			out("< LOOP");
		}
	| #(POUND (num:. {
			out("> POUND");
			r.setType(DataType.Number);
			r.setDataList(modifier(#num));
			out("< POUND");
		})*)
	| #(AT (letter:. {
			out("> AT");
			r.setType(DataType.Letter);
			r.setDataList(modifier(#letter));
			out("< AT");
		})*)
	| #(AMPERSAND (alphanumeric:. {
			out("> AMPERSAND");
			r.setType(DataType.AlphaNumeric);
			r.setDataList(modifier(#alphanumeric));
			out("< AMPERSAND");
		})*)
	| #(DOLLAR (symbol:. {
			out("> DOLLAR");
			r.setType(DataType.Symbol);
			r.setDataList(modifier(#symbol));
			out("< DOLLAR");
		})*)
	| #(PERCENT (wildcard:. {
			out("> PERCENT");
			r.setType(DataType.Any);
			r.setDataList(modifier(#wildcard));
			out("< PERCENT");
		})*)
	| #(ENUMERATION (enu:. {
			out("> ENUMERATION");
			r.setType(DataType.Enum);
			r.setDataList(enumeration(#enu));
			out("< ENUMERATION");
		})*)
	;

modifier returns [ DataList length ]
{
	length = new DataList();
}
	: #(LENGTH (rng:. {
		out("> LENGTH");
		length.add(length(#rng));
		out("< LENGTH");
		})*)
	;

length returns [ List<String> values ]
{
	values = new ArrayList<String>();
	List<String> a, b;
}
	: num:NUMBER {
			out("> NUMBER");
			String number = num.getText();
			out("Number: " + number);
			values.add(number);
			out("< NUMBER");
		}
	| val:WORD {
			out("> WORD");
			String value = val.getText();
			out("Value: " + value);
			values.add(value);
			out("< WORD");
		}
	| #(MINUS a=length b=length) {
			int start = Integer.parseInt(a.get(0));
			int end = Integer.parseInt(b.get(0));
			
			if(start > end) {
				int temp = start;
				start = end;
				end = temp;
			}
			
			for(int i = start; i <= end; i++) {
				values.add(i + "");
			}
		}
	;

enumeration returns [ DataList length ]
{
	length = new DataList();
}
	: #(QUESTION (ques:. {
			out("> QUESTION");
			length.add(length(#ques));
			out("< QUESTION");
		})*)
	| #(ASTERISK (star:. {
			out("> ASTERISK");
			length.add(length(#star));
			// create an empty item in the list for nullable enumeration
			List<String> list = new ArrayList<String>();
			list.add("");
			length.add(list);	
			out("< ASTERISK");
		})*)
	;
